package sui.utils.freemarker;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.io.StringWriter;
import java.io.Writer;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import freemarker.template.TemplateExceptionHandler;

/**
 * <p>
 * Description: FreeMarker工具类
 * </p>
 * @author XQF SUI
 * @created 2016年9月28日 下午2:05:03
 * @version 1.0
 */
public class FreeMarkerUtils {

    private static Logger logger = LoggerFactory.getLogger(FreeMarkerUtils.class);

    private static Configuration cfg;
    private static Template temp;

    /**
     * <p>
     * Desc: 创建Configuration
     * <p>
     * @author XQF SUI
     * @created 2016年9月28日 下午5:24:53
     * @throws IOException
     * @throws TemplateException
     */
    public static void createConfiguration() {
        logger.info("开始创建Configuration...");
//        cfg = new Configuration(Configuration.VERSION_2_3_22);
        cfg = new Configuration();
    }

    /**
     * <p>
     * Desc: 加载模板
     * <p>
     * @author XQF SUI
     * @created 2016年9月28日 下午5:25:06
     * @param templateDic
     * @param templateName
     * @return
     * @throws IOException
     * @throws TemplateException
     */
    public static boolean loadingTemplate(String templateDic, String templateName) {
        createConfiguration();

        logger.info("开始加载模板...");

        try {
            cfg.setDirectoryForTemplateLoading(new File(FreeMarkerUtils.class.getClassLoader().getResource("../../" + templateDic).getFile()));
            cfg.setDefaultEncoding("UTF-8");
            cfg.setTemplateExceptionHandler(TemplateExceptionHandler.RETHROW_HANDLER);

            temp = cfg.getTemplate(templateName);
        } catch (Exception e) {
            logger.error("加载模板失败", e);
            return false;
        }

        return true;
    }

    /**
     * <p>
     * Desc: 生成HTML文件
     * <p>
     * @author XQF SUI
     * @created 2016年9月28日 下午5:25:26
     * @param paramMap              模板参数
     * @param templateDic           模板目录
     * @param templateName          模板名称
     * @param outFile               输出文件
     * @throws TemplateException
     * @throws IOException
     */
    public static boolean generateHTML(Map<String, Object> paramMap, String templateDic, String templateName,
                                       String outFile) {

        logger.info("调用FreeMarker生成HTML文件, 入参:[ {} ][ {} ][ {} ][ {} ]", paramMap, templateDic, templateName, outFile);

        if (!loadingTemplate(templateDic, templateName)) {
            logger.info("FreeMarker生成HTML文件[ {} ]失败", outFile);
            return false;
        }

        try {
            temp.process(paramMap, new OutputStreamWriter(new FileOutputStream(outFile)));
        } catch (Exception e) {
            logger.error("FreeMarker生成HTML文件[ {} ]失败", outFile, e);
            return false;
        }

        logger.info("FreeMarker生成HTML文件[ {} ]成功", outFile);

        return true;
    }
    
    /**
     * <p>
     * Desc: 生成HTML文件
     * <p>
     * @author XQF SUI
     * @created 2016年9月28日 下午5:25:26
     * @param paramMap              模板参数
     * @param templateDic           模板目录
     * @param templateName          模板名称
     * @param outFile               输出文件
     * @throws TemplateException
     * @throws IOException
     */
    public static String generateWriterString(Map<String, Object> paramMap, String templateDic, String templateName) {

        logger.info("调用FreeMarker生成HTML文件, 入参:[ {} ][ {} ][ {} ]", paramMap, templateDic, templateName);

        if (!loadingTemplate(templateDic, templateName)) {
            logger.info("FreeMarker生成HTML文件失败");
            return null;
        }
        
        Writer out = new StringWriter();

        try {
            temp.process(paramMap, out);
        } catch (Exception e) {
            logger.error("FreeMarker生成HTML文件失败", e);
        }

        logger.info("FreeMarker生成HTML文件成功");

        return out.toString();
    }
}
